package jee.boot.module.log.service;

import jee.boot.common.basic.CrudService;
import jee.boot.common.basic.Page;
import jee.boot.common.basic.ServiceException;
import jee.boot.common.utils.JsonMapper;
import jee.boot.common.utils.StringUtils;
import jee.boot.module.elasticsearch.entity.Document;
import jee.boot.module.elasticsearch.utils.ElasticsearchUtils;
import jee.boot.module.log.dao.LogEntityDao;
import jee.boot.entity.log.LogEntity;
import org.elasticsearch.action.get.GetResponse;
import org.elasticsearch.action.search.SearchResponse;
import org.elasticsearch.index.query.BoolQueryBuilder;
import org.elasticsearch.index.query.QueryBuilders;
import org.elasticsearch.search.SearchHit;
import org.elasticsearch.search.builder.SearchSourceBuilder;
import org.elasticsearch.search.sort.SortOrder;
import org.springframework.stereotype.Service;

import java.util.Map;

@Service
public class LogEntityService extends CrudService<LogEntityDao, LogEntity> {
    // 日志留痕默认的索引名称
    private static  final String TRACE_LOG_INDEX="trace";
    /**
     * 获取详情重写
     * @param entity
     * @return
     */
    public LogEntity get(LogEntity entity) {
        Document data=new Document();
        data.setIndexName(TRACE_LOG_INDEX);
        data.setId(entity.getId());
        //查询es搜索引擎获取详情
        GetResponse doc = ElasticsearchUtils.get(data);
        if(doc.isExists()){
            Map<String, Object> source = doc.getSource();
            entity.setProjectName((String)source.get("traceProjectName"));
            entity.setRemoteAddr((String)source.get("traceRemoteAddr"));
            entity.setServiceName((String)source.get("traceServiceName"));
            entity.setOperator((String)source.get("traceOperator"));
            entity.setEntityName((String)source.get("traceEntityName"));
            entity.setEntityId((String)source.get("traceEntityId"));
            entity.setEntity(JsonMapper.fromJsonString((String)source.get("traceEntity"),Map.class));
        }
        return entity;
    }

    /**
     * 分页查询重写
     * @param entity
     * @return
     */
    @Override
    public Page<LogEntity> findPage(LogEntity entity) {
        SearchSourceBuilder builder = new SearchSourceBuilder();
        Document data = new Document();
        data.setIndexName(TRACE_LOG_INDEX);
        // 分页设置
        //计算起始行
        int from = entity.getPage().getPageNo() > 0 ? (entity.getPage().getPageNo() - 1) * entity.getPage().getPageSize() : 0;
        builder.from(from);
        builder.size(entity.getPage().getPageSize());
        // 设置排序,这里就固定elk读取日志的时间为准,目前不支持使用其他字段
        builder.sort("@timestamp", SortOrder.DESC);
        // 设置查询条件
        BoolQueryBuilder mustQuery = QueryBuilders.boolQuery();
        mustQuery.must(QueryBuilders.matchQuery("traceEntityName", entity.getEntityName()));
        mustQuery.must(QueryBuilders.matchQuery("traceProjectName", entity.getProjectName()));
        mustQuery.must(QueryBuilders.matchQuery("traceEntityId", entity.getEntityId()));
        if(StringUtils.isNotBlank(entity.getSearch())){
            mustQuery.must(QueryBuilders.matchQuery("traceEntity",entity.getSearch()));
        }
        builder.query(mustQuery);
        // 数据回填------------------
        SearchResponse doc = ElasticsearchUtils.search(data, builder);
        // 设置总条数
        entity.getPage().setCount(doc.getHits().getTotalHits().value);
        SearchHit[] hits = doc.getHits().getHits();
        if(hits.length>0){
            for(SearchHit hit:hits){
                LogEntity e=new LogEntity();
                Map<String, Object> sourceAsMap = hit.getSourceAsMap();
                e.setId(hit.getId());
                e.setEntityId((String)sourceAsMap.get("traceEntityId"));
                e.setEntityName((String)sourceAsMap.get("traceEntityName"));
                e.setOperator((String)sourceAsMap.get("traceOperator"));
                e.setProjectName((String)sourceAsMap.get("traceProjectName"));
                e.setRemoteAddr((String)sourceAsMap.get("traceRemoteAddr"));
                e.setServiceName((String)sourceAsMap.get("traceServiceName"));
                e.setEntity(JsonMapper.fromJsonString((String)sourceAsMap.get("traceEntity"),Map.class));
                entity.getPage().getList().add(e);
            }
        }
        return entity.getPage();
    }
     /**
     * 删除重写
     * @param entity
     */
    @Override
    public void delete(LogEntity entity) {
        Document data=new Document();
        data.setIndexName(TRACE_LOG_INDEX);
        data.setId(entity.getId());
        //删除es搜索引擎获中的数据
        ElasticsearchUtils.delete(data);
    }
    @Override
    public void save(LogEntity entity) {
        throw new ServiceException(1406);
    }
    @Override
    public void update(LogEntity entity) {
        throw new ServiceException(1407);

    }

    /**
     * 插入本地log
     * @param log
     */
    public void insertLocalLog( Map<String, Object> log){
        dao.insertLocalLog(log);
    }
}
